var sw = 15,//宽
    sh = 15,//高
    row = 28,//行数
    lie = 20//列

var snake;
var food;
var game;

//每一个 方块的 构造函数
function Square(x, y, classname) {

    this.x = x * sw;
    this.y = y * sh;
    this.class = classname;
    //对应的dom元素

    this.viewContent = document.createElement("div");
    this.viewContent.className = this.class;//classname
    this.parent = document.getElementById("game-box");
}
//添加 到dom结构中
Square.prototype.create = function () {
    this.viewContent.style.height = sh + "px";
    this.viewContent.style.position = "absolute";
    this.viewContent.style.width = sw + "px";
    this.viewContent.style.left = this.x + "px";
    this.viewContent.style.top = this.y + "px";
    //添加到 dom树当中
    this.parent.appendChild(this.viewContent);
};

Square.prototype.remove = function () {
    this.parent.removeChild(this.viewContent);
};


function Snake() {
    this.head = null;
    this.tail = null;

    this.pos = []; //储存  蛇每一个节点的位置
    this.directionNum = {      //存储可能方向的数字描述对象
        up: {
            x: 0,
            y: -1,
            rotate: 180
        },
        down: {
            x: 0,
            y: 1,
            rotate: 0
        },
        left: {
            x: -1,
            y: 0,
            rotate: 90
        },
        right: {
            x: 1,
            y: 0,
            rotate: -90
        }

    }
};

//初始化 蛇
Snake.prototype.init = function () {

    //创建并更新蛇头
    var snakeHead = new Square(2, 0, "snake-head");
    snakeHead.create();
    this.head = snakeHead;
    this.pos.push([2, 0]);


    //创建 并更新 身体

    var snakeBody1 = new Square(1, 0, "snake-body");
    snakeBody1.create();
    this.pos.push([1, 0]);


    var snakeBody2 = new Square(0, 0, "snake-body");
    snakeBody2.create();
    this.pos.push([0, 0]);

    snakeHead.last = null;
    snakeHead.next = snakeBody1;
    snakeBody1.last = snakeHead;
    snakeBody1.next = snakeBody2;

    this.tail = snakeBody2;
    snakeBody2.last = snakeBody1;
    snakeBody2.next = null;

    //初始化 蛇的时候添加 属性 即将走的方向  默认 方向是 向右
    this.direction = this.directionNum.right;

};



Snake.prototype.getNextPos = function () {
    //得到下一个位置
    var nextPos = [
        this.head.x / sw + this.direction.x, this.head.y / sh + this.direction.y
    ];

    //检测是否撞到了自己
    var selfCollid = false;
    this.pos.forEach(function (value) {
        if (value[0] == nextPos[0] && value[1] == nextPos[1]) {
            selfCollid = true;
        }

    });
    if (selfCollid) {
        console.log("撞到自己了");
        this.strategies.die.call(this);
        return;
    }
    //墙
    //检测是否 撞墙
    if (nextPos[0] < 0 || nextPos[1] < 0 || nextPos[0] > lie - 1 || nextPos[1] > row - 1) {
        console.log("撞墙了");
        this.strategies.die.call(this);
        return;
    }
    //食物

    if (food && food.pos[0] == nextPos[0] && food.pos[1] == nextPos[1]) {
        this.strategies.eat.call(this);
        console.log("撞到食物");
        return;
    }



    //移动
    this.strategies.move.call(this, true);


}


Snake.prototype.strategies = {
    move: function (isDeleted) {
        //创建新蛇头
        var newHead = new Square(this.head.x / sw + this.direction.x, this.head.y / sh + this.direction.y, "snake-head");
        newHead.viewContent.style.transform = "rotate(" + this.direction.rotate + "deg)";
        //创建新身体
        var newBody = new Square(this.head.x / sw, this.head.y / sh, "snake-body");

        //更新链表结构
        newBody.next = this.head.next;
        newBody.next.last = newBody;

        newBody.last = newHead;
        newHead.next = newBody;
        newHead.last = null;

        this.head.remove();
        newBody.create();
        newHead.create();

        //更新Pos,插入 新蛇头就可以
        this.pos.splice(0, 0, [this.head.x / sw + this.direction.x, this.head.y / sh + this.direction.y]);
        this.head = newHead;

        if (isDeleted)//判定是否要删除 最后一个节点     必须要传入这个赞数
        {
            this.tail.remove();
            this.tail = this.tail.last;
            this.pos.pop();
        }




    },
    eat: function () {
        this.strategies.move.call(this, false);
        createFood();
        game.score++;
        var t = parseInt(score.getAttribute("value"));
        score.setAttribute("value", t + 1 + "");
    },
    die: function () {
        game.over();
    }
}




//创建食物
function createFood() {
    var x;
    var y;
    var include = true;
    //随机生成 位置 保证 x  ，y 不在蛇的身体里面
    while (include) {
        x = parseInt(Math.random() * lie);
        y = parseInt(Math.random() * row);
        snake.pos.forEach(function (value) {

            if (value[0] != x && value[1] != y) {
                include = false;
            }
        });
    }
    food = new Square(x, y, "food");
    food.pos = [x, y];//用于检测是否 碰上食物

    var foodDom = document.querySelector(".food");//若 已经存在食物，只需更改 top，left的值 
    if (foodDom) {
        foodDom.style.left = x * sw + "px";
        foodDom.style.top = y * sh + "px";
    }
    else {//若不存食物，则就是 刚开始游戏的时候 ，
        food.create();
    }

}


function Game() {
    this.timer = null;//定时器
    this.score = 0;
}
Game.prototype.init = function () {
    snake.init();
    createFood();
    //绑定  键盘事件
    document.addEventListener("keydown", function (event) {
        if (event.which == 37 && snake.direction != snake.directionNum.right)//左键
        {
            snake.direction = snake.directionNum.left;
        }
        else if (event.which == 38 && snake.direction != snake.directionNum.down)//上键
        {
            snake.direction = snake.directionNum.up;
        }
        else if (event.which == 39 && snake.direction != snake.directionNum.left)//右键
        {
            snake.direction = snake.directionNum.right;
        }
        else if (event.which == 40 && snake.direction != snake.directionNum.up)//下键
        {
            snake.direction = snake.directionNum.down;
        }
    }, false);
    this.start();
}
Game.prototype.start = function () {
    score.setAttribute("value","0");
    this.timer = setInterval(function () {
        snake.getNextPos();

    }, 200);
}

Game.prototype.over = function () {
    score.setAttribute("value","0");
    clearInterval(this.timer);
    alert("得分" + this.score);
    //清除 游戏  重新开始
    var gameBox = document.getElementById("game-box");
    gameBox.innerHTML = "";
    game = new Game();
    snake = new Snake();
    startBtn.parentNode.style.display = "block";
   

}
Game.prototype.pause = function () {
    clearInterval(this.timer);
}
snake = new Snake();
game = new Game();
var startBtn = document.querySelector(".startBtn button");
startBtn.addEventListener("click", function () {
    this.parentNode.style.display = "none";
    game.init();
}, false);

var pauseBtn = document.querySelector(".pauseBtn button");
var gameBox = document.getElementById("game-box");
//添加暂停事件
gameBox.addEventListener("click", function () {

    game.pause();

    pauseBtn.parentNode.style.display = "block";
}, false);
//添加继续事件
pauseBtn.addEventListener("click", function () {

    this.parentNode.style.display = "none";
    game.start();
}, false);

var score = document.querySelector(".score input");

var up_B = document.querySelector(".up");
var down_B = document.querySelector(".down");
var left_B = document.querySelector(".left");
var right_B = document.querySelector(".right");
//绑定按钮的 触摸事件
up_B.addEventListener("touchstart", function () {
    snake.direction = snake.directionNum.up;
    this.style.backgroundColor = "rgba(0,0,0,0.3)";
}, false);
up_B.addEventListener("touchend", function () {
    this.style.backgroundColor = "transparent";
}, false);

down_B.addEventListener("touchstart", function () {
    snake.direction = snake.directionNum.down;
    this.style.backgroundColor = "rgba(0,0,0,0.3)";
}, false);
down_B.addEventListener("touchend", function () {
    this.style.backgroundColor = "transparent";
}, false);

left_B.addEventListener("touchstart", function () {
    snake.direction = snake.directionNum.left;
    this.style.backgroundColor = "rgba(0,0,0,0.3)";
}, false);
left_B.addEventListener("touchend", function () {

    this.style.backgroundColor = "transparent";
}, false);
right_B.addEventListener("touchstart", function () {
    snake.direction = snake.directionNum.right;
    this.style.backgroundColor = "rgba(0,0,0,0.3)";
}, false);
right_B.addEventListener("touchend", function () {
    this.style.backgroundColor = "transparent";
}, false);